package com.guiji.text2video.job.task;

import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpResponse;
import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.guiji.text2video.job.domain.LongVideoBO;
import com.guiji.text2video.job.domain.Text2videoConfig;
import com.guiji.text2video.job.domain.Text2videoJob;
import com.guiji.text2video.job.mapper.SpiderNewsStatMapper;
import com.guiji.text2video.job.mapper.Text2videoConfigMapper;
import com.guiji.text2video.job.mapper.Text2videoJobMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;

/**
 * @Copyright (C), 2018-2022
 * @FileName: LongVideoTask
 * @Author: scl
 * @Date: 2022/1/10 9:21
 * @Description: 长视频合成策略
 */
@RefreshScope
@Component("lvt")
public class LongVideoTask {

    private static final Logger logger = LoggerFactory.getLogger(LongVideoTask.class);

    private static String pathUrl = "http://172.16.160.54/text2video/longVideos/";

    @Autowired(required = false)
    SpiderNewsStatMapper spiderNewsStatMapper;

    @Autowired(required = false)
    Text2videoJobMapper jobMapper;

    @Autowired(required = false)
    Text2videoConfigMapper configMapper;

    @Autowired
    PushTask pushTask;

    @Value("${file-cache.longvideo-url}")
    private String longVideoURL;

    @Value("${file-cache.youtuberank-url}")
    private String youtuberankURL;

    /**
     * @descp: 推送已经合成的视频。所有视频
     * @param:
     * @Author: scl
     * @Date: 2022/1/19 10:47
     */
    public void gTLV(String youtubeAccount, String channel) {
        Text2videoJob job = new Text2videoJob();
        job.setIsSuccess("1");
        job.setBackupText("Day-HotNews-Collection");
        job.setBackup1(youtubeAccount);
        List<Text2videoJob> jobs = jobMapper.selectText2videoJobList(job);
    }

    /**
     * @descp: 账号，-1表示昨天，0表示今天，1表示明天，几个视频合成
     * @param:lvt.gTLV('Asian Tech Info', 'asiantechinfo',0, 10)
     * @Author: scl
     * @Date: 2022/1/14 14:26
     */
    public void gTLV(String youtubeAccount, String channel, Integer dayBeforeStart, Integer top10) {

        DateTime time = DateUtil.offsetDay(DateUtil.tomorrow(), dayBeforeStart - 1);
        logger.info("time:{}", time);
        //1,账号找到youtube链接。
        List<Text2videoConfig> lastConfig = getYouTuBeAccount(youtubeAccount);
        if (null == lastConfig) {
            logger.info("每日长视频，找不到config配置:{}", youtubeAccount);
            return;
        }
        //2,账号找到今天日期的视频拼凑成。
        List<Text2videoJob> jobs = new ArrayList<>();
        for (Text2videoConfig c : lastConfig) {
            Text2videoJob job = new Text2videoJob();
            //and  DATE_FORMAT(create_time, '%Y-%m-%d') = DATE_FORMAT(#{createTime},'%Y-%m-%d')
            job.setCreateTime(new Date());
            job.setIsSuccess("1");
            job.setBackupText(c.getNewsCategory());
            jobs.addAll(jobMapper.selectText2videoJobList(job));
        }
        logger.info("合成的视频个数：{}", jobs.size());
        //3,过滤新闻
        List<Text2videoJob> pushJobs = getSize(jobs, top10);
        if (null == pushJobs) {
            logger.info("集合太小终止方法");
            return;
        }
        ArrayList<String> links = new ArrayList<>();
        for (Text2videoJob job : pushJobs) {
            job.setIsSuccess("2");
            jobMapper.updateText2videoJob(job);
            links.add(job.getBackup2());
        }

        //4,上传
        String timeStr = DateUtil.format(time, "yyyy-MM-dd:hh");

        //标题
        String longTitle = timeStr + "每日新闻集合";
        if (lastConfig.get(0).getNewsLang() == 1) {
            longTitle = timeStr + " Daily News Collection";
        }
        LongVideoBO lv = new LongVideoBO();
        lv.setNewsCategory(longTitle);
        lv.setVideos(links);
        lv.setVideoHead("");
        lv.setVideoTail("");
        lv.setVideoSegmentation("");
        HttpResponse longRequest = getLongVideo(lv);
        JSONObject longJsonObject = JSON.parseObject(longRequest.body());
        JSONArray tailsArray = longJsonObject.getJSONArray("tails");
        String fileName = (String) longJsonObject.get("filename");
        String description = "";
        for (int a = 0; a < tailsArray.size(); a++) {
            String tail = (String) tailsArray.get(a);
            description = description + tail + " " + pushJobs.get(a).getTitle() + "\n";
        }

        logger.info("每日长视频标题:{},长视频链接:{},description内容是:{}", longTitle, pathUrl + fileName, description);
        List<Text2videoJob> listJobs = new ArrayList<>();

        Text2videoJob job = new Text2videoJob();
        job.setJobId(fileName.replace(".mp4", ""));
        job.setTitle(longTitle);
        job.setContent(description);
        job.setIsSuccess("1");
        job.setBackupText("Day-HotNews-Collection");
        job.setBackup1(youtubeAccount);
        job.setBackup2(pathUrl + fileName);
        job.setCreateTime(new Date());
        jobMapper.insertText2videoJob(job);
        listJobs.add(job);
        pushTask.getTop5(listJobs, channel, lastConfig.get(0).getBackup2(), ":5556/api/upload");
    }


    public List<Text2videoJob> getSize(List<Text2videoJob> jobs, int top10) {
        if (jobs.size() < 5) {
            return null;
        }
        if (jobs.size() < top10) {
            return jobs;
        }
        return jobs.subList(0, top10);
    }


    /**
     * @descp: -1表示昨天，0表示今天，1表示明天
     * @param:
     * @Author: scl
     * @Date: 2022/1/10 11:41
     */
    public void getVideoTop10(String youtubeAccount, String channel, Integer dayBeforeStart, Integer top10) throws InterruptedException {

        dayBeforeStart = dayBeforeStart - 1;
        String time = DateUtil.format(DateUtil.offsetDay(DateUtil.tomorrow(), dayBeforeStart), "yyyy-MM-dd");
        logger.info("time:{}", time);
        //1,账号找到youtube链接。
        List<Text2videoConfig> list = getYouTuBeAccount(youtubeAccount);
        if (null == list) {
            return;
        }
        Text2videoConfig lastConfig = list.get(0);
        //2,获取排名靠前视频
        HttpResponse response = null;
        int tryCount = 0;
        while (true) {
            response = getHttp(lastConfig.getBackup5(), time, top10);
            if (ObjectUtil.isNotEmpty(response) && response.getStatus() == 200) {
                break;
            } else if (ObjectUtil.isEmpty(response) || response.getStatus() == 500) {
                tryCount++;
                Thread.sleep(10000);
            }
            if (tryCount == 10) {
                logger.info("排行接口调用:{}次,依然失败终止方法", tryCount);
                return;
            }
        }
        HashMap<String, String> map = new HashMap<>();
        ArrayList<String> links = new ArrayList<>();
        logger.info("youtube排行接口数据:{}", response.body());
        JSONObject jsonObject = JSON.parseObject(response.body());
        JSONArray array = jsonObject.getJSONArray("data");
        if (null == array) {
            logger.info("youtube排行接口找不到data数据:{}", response.body());
            return;
        }
        for (int a = 0; a < array.size(); a++) {
            String title = (String) array.getJSONObject(a).get("title");

            Text2videoJob job = new Text2videoJob();
            job.setTitle(title);
            job.setIsSuccess("2");
            List<Text2videoJob> jobList = jobMapper.selectText2videoJobList(job);
            if (jobList.size() == 1) {
                map.put(jobList.get(0).getBackup2(), jobList.get(0).getTitle());
                links.add(jobList.get(0).getBackup2());
            }
        }

        //3,合成服务

        int week = DateUtil.thisWeekOfYear() - 1;
        String taskTitle = "2022年第" + week + "周热点新闻集合";
        if (lastConfig.getNewsLang() == 1) {
            taskTitle = "2022 Week " + week + " hot news collection";
        }

        LongVideoBO lv = new LongVideoBO();
        lv.setNewsCategory(taskTitle);
        lv.setVideos(links);
        lv.setVideoHead("");
        lv.setVideoTail("");
        lv.setVideoSegmentation("");
        HttpResponse longRequest = getLongVideo(lv);
        //{"filename":"Vfrl3qQR_0111_100905.mp4","taskId":"Wee-20220104-164218-548338765488","times":["t=0s","t=63s"],"tails":["0:00","1:03"]}
        JSONObject longJsonObject = JSON.parseObject(longRequest.body());
        JSONArray tailsArray = longJsonObject.getJSONArray("tails");
        String fileName = (String) longJsonObject.get("filename");
        String description = "";
        for (int a = 0; a < tailsArray.size(); a++) {
            String tail = (String) tailsArray.get(a);
            description = description + tail + " " + map.get(links.get(a)) + "\n";
        }
        //4,推送服务
        //组装description,taskTitle,pathUrl+fileName
        logger.info("每周长视频标题:{},长视频链接:{},description内容是:{}", taskTitle, pathUrl + fileName, description);
        List<Text2videoJob> listJobs = new ArrayList<>();

        Text2videoJob job = new Text2videoJob();
        job.setJobId(fileName.replace(".mp4", ""));
        job.setTitle(taskTitle);
        job.setContent(description);
        job.setIsSuccess("1");
        job.setBackupText("Week-HotNews-Collection");
        job.setBackup1(youtubeAccount);
        job.setBackup2(pathUrl + fileName);
        job.setCreateTime(new Date());
        jobMapper.insertText2videoJob(job);
        listJobs.add(job);
        pushTask.getTop5(listJobs, channel, lastConfig.getBackup2(), ":5556/api/upload");

    }

    private HttpResponse getHttp(String youtubeUrl, String time, int top10) {

        String url = youtuberankURL;
        url = url + "?url=" + youtubeUrl + "&startTime=" + time + "&rankViewCount=" + top10;
        HttpResponse httpResponse = null;
        try {
            httpResponse = HttpRequest.get(url).timeout(600000).execute();
        } catch (Exception e) {
            logger.info("youtube排名http异常！");
        }
        //继续执行，可能为null
        return httpResponse;
    }


    public HttpResponse getLongVideo(LongVideoBO lv) {

        HttpResponse httpResponse = null;
        logger.info("发起长视频请求,对象:{}", JSONUtil.parseObj(lv).toString());
        try {
            httpResponse = HttpRequest.post(longVideoURL).timeout(7200000).body(JSONUtil.parseObj(lv).toString()).executeAsync();
        } catch (Exception e) {
            logger.info("长视频http请求异常:{}", e.toString());
        }
        if (ObjectUtil.isNotEmpty(httpResponse) && httpResponse.getStatus() == 200) {
            return httpResponse;
        }
        return httpResponse;
    }

    private List<Text2videoConfig> getYouTuBeAccount(String youtubeAccount) {
        List<Text2videoConfig> results = new ArrayList();
        Text2videoConfig config = new Text2videoConfig();
        config.setBackup1(youtubeAccount);
        Text2videoConfig lastConfig = null;
        List<Text2videoConfig> text2videoConfigList = configMapper.selectText2videoConfigList(config);
        for (Text2videoConfig c : text2videoConfigList) {
            if (ObjectUtil.isNotEmpty(c.getBackup5()) && c.getNewsLang() != -1) {
                results.add(c);
                break;
            }
        }
        if (ObjectUtil.isEmpty(results)) {
            logger.info("找不到config配置youtube:{}", youtubeAccount);
            return null;
        }
        return results;
    }

}